package orm

import (
	"database/sql"
	"fmt"
	"github.com/jinzhu/gorm"
	_ "github.com/jinzhu/gorm/dialects/mysql"
	"github.com/sirupsen/logrus"
	"time"
)

type GormFunc struct {
	db *gorm.DB
}

func (g GormFunc) Query(sql string, params []interface{}) *sql.Rows{
	fmt.Println(g.db)
	rows, err := g.db.Raw(sql,params...).Rows()
	if err!=nil{
		logrus.Error(err)
		return nil
	}
	return rows
}

func (g GormFunc) Insert(sql string, params interface{}) int {
	panic("implement me")
}

func (g GormFunc) Update(sql string, params interface{}) bool {
	panic("implement me")
}

func (g GormFunc) Delete(sql string, params interface{}) bool {
	panic("implement me")
}

func newGorm()OrmFunc{
	return func(userName string, passWord string, url string, database string) OrmInfuraInter {
		db,err:=gorm.Open("mysql", fmt.Sprintf("%s:%s@tcp(%s)/%s?charset=utf8&parseTime=True&loc=Local&timeout=10s",
			userName,
			passWord,
			url,
			database))

		if err!=nil{
			panic(fmt.Sprintf("open datasource error:%v",err))
		}

		//gorm.DefaultTableNameHandler = func(db *gorm.DB, defaultTableName string) string {
		//	return table_prefix + defaultTableName
		//}

		//打印日志
		db.LogMode(true)
		db.SingularTable(true)
		db.Callback().Create().Replace("gorm:created_at", updateTimeStampForCreateCallback)
		db.Callback().Update().Replace("gorm:updated_at", updateTimeStampForUpdateCallback)
		//db.Callback().Delete().Replace("gorm:delete", deleteCallback)
		db.DB().SetMaxIdleConns(10)
		db.DB().SetMaxOpenConns(100)
		db.DB().SetConnMaxLifetime(time.Second * 600)
		
		return GormFunc{
			db: db,
		}
	}
}

// updateTimeStampForCreateCallback will set `CreatedOn`, `ModifiedOn` when creating
func updateTimeStampForCreateCallback(scope *gorm.Scope) {
	if !scope.HasError() {
		nowTime := time.Now().Unix()
		if createTimeField, ok := scope.FieldByName("CreatedOn"); ok {
			if createTimeField.IsBlank {
				createTimeField.Set(nowTime)
			}
		}

		if modifyTimeField, ok := scope.FieldByName("ModifiedOn"); ok {
			if modifyTimeField.IsBlank {
				modifyTimeField.Set(nowTime)
			}
		}
	}
}

// updateTimeStampForUpdateCallback will set `ModifiedOn` when updating
func updateTimeStampForUpdateCallback(scope *gorm.Scope) {
	if _, ok := scope.Get("gorm:update_column"); !ok {
		scope.SetColumn("ModifiedOn", time.Now().Unix())
	}
}